# 导入所需的调度器类和触发器类
from apscheduler.schedulers.background import BackgroundScheduler #后台运行
from apscheduler.schedulers.blocking import BlockingScheduler  #主进程运行，需要单独运行
from apscheduler.triggers.interval import IntervalTrigger #时间间隔
from apscheduler.triggers.cron import CronTrigger #复杂的定时任务
from apscheduler.triggers.date import DateTrigger #一次性定时任务
from django.core.management.base import BaseCommand
from apscheduler import events
from pytz import timezone
from threading import RLock
from datetime import datetime, timedelta
from gs_scheduler.models import MysqlDB
#定时任务
from .task import delete_apscheduler_history
from .task import send_to_big_data
#日志
from utils.log_util import info_log
from .config import LISTENER
from .config import TIME_ZONE,JOB_DEFAULTS,JOB_STORE

#脚本运行：python manage.py crontab
class Command(BaseCommand):
    TIME_FORMAT = '%Y-%m-%d %H:%M:%S'
    #初始化调度器
    def _scheduler_obj(self):
        scheduler = BlockingScheduler()
        scheduler.configure(
            timezone = TIME_ZONE, #时区
            job_defaults=JOB_DEFAULTS, #job的默认配置
            jobstores=JOB_STORE, #job的存储后端
        )
        return scheduler

    #添加任务
    def _add_job(self,scheduler:BlockingScheduler):
        #每5分钟执行一次推送告警到大数据仓
        scheduler.add_job(
            send_to_big_data,
            trigger=IntervalTrigger(minutes=1),
            id='send_to_big_data',
            replace_existing=True,
            coalesce=True,
        )
        #每隔8个小时，清除历史的记录
        scheduler.add_job(
            delete_apscheduler_history,
            trigger=IntervalTrigger(hours=8),
            id='delete_apscheduler_history',
            replace_existing=True,
            coalesce=True,
        )

    #添加监听器
    def _listener(self,event:events):
        code = event.code
        run_time = datetime.now().strftime(self.TIME_FORMAT)
        msg = LISTENER.get(code)
        db = MysqlDB()
        if msg:
            if code == 4096:
                #成功运行
                job_id = event.job_id
                #记录到数据库中
                db.insert_into_apscheduler_history([job_id,run_time,0])
            elif code == 8192:
                #运行异常了
                job_id = event.job_id
                #记录到数据库中
                db.insert_into_apscheduler_history([job_id,run_time,1,msg])
            else:
                info_log(msg)
        db.close()
    def start(self):
        scheduler = self._scheduler_obj()
        # 创建记录运行记录
        db = MysqlDB()
        db.create_apscheduler_history()
        db.close()
        # 设置监听器
        scheduler.add_listener(self._listener)
        # 设置定时任务
        self._add_job(scheduler)
        try:
            # print('{},定时器启动成功,等待定时任务执行...'.format(datetime.now().strftime(self.TIME_FORMAT)))
            scheduler.start()
        except KeyboardInterrupt:
            scheduler.shutdown()

    # python manage.py crontab运行 就是调用该方法
    def handle(self, *args, **options):
        self.start()

#伴随django，在后台运行的。 在wsgi.py 文件中，调用BackRunScheduler().start()
class BackRunScheduler(Command):
    # 初始化调度器
    def _scheduler_obj(self):
        scheduler = BackgroundScheduler()
        scheduler.configure(
            timezone=TIME_ZONE,  # 时区
            job_defaults=JOB_DEFAULTS,  # job的默认配置
            jobstores=JOB_STORE,  # job的存储后端
        )
        return scheduler